import { defineStore } from 'pinia'
import { ref, watch } from 'vue'
import { agencyAsync, appoxEnums } from '@/appox/appox'
import { DialogQueue } from '@/utils/dialogQueue'

export const useSignalAdderStore = defineStore('signalAdder', () => {
  // 状态
  const dialogQueue = new DialogQueue()
  const searchKey = ref('')
  const treeData = ref([])
  const availableCount = ref(0)
  const originSelectedIds = []
  const newSelectedIds = []

  async function updateTreeData(key) {
    const signalTree = await agencyAsync.getSignalTree()
    if (!signalTree) {
      treeData.value = []
      return
    }

    const topNodes = []
    const keyLower = key.toLowerCase()
    const keyValid = key.length >= 2

    const allSelectedIDs = []
    allSelectedIDs.push(...originSelectedIds)
    allSelectedIDs.push(...newSelectedIds)

    for (const top of signalTree) {
      const topMatch = keyValid && (top.id.toLowerCase().includes(keyLower) || top.name.toLowerCase().includes(keyLower))
      const topNode = {
        id: top.id,
        name: top.name,
        children: []
      }
      let shouldAddTopNode = !keyValid || topMatch

      if (top.children) {
        for (const middle of top.children) {
          const middleMatch = keyValid && (middle.id.toLowerCase().includes(keyLower) || middle.name.toLowerCase().includes(keyLower))
          
          const middleNode = {
            id: middle.id,
            name: middle.name,
            children: []
          }
          let shouldAddMiddleNode = !keyValid || topMatch || middleMatch

          if (middle.children) {
            for (const signal of middle.children) {
              const signalMatch = keyValid && (signal.id.toLowerCase().includes(keyLower) || signal.name.toLowerCase().includes(keyLower))
              const isAdded = signal.type >= appoxEnums.SignalTreeNodeType.GeneralSignal && allSelectedIDs.includes(signal.id)

              const signalNode = {
                id: signal.id,
                name: signal.name,
                exist: isAdded
              }
              const shouldAddSignalNode = !keyValid || topMatch || middleMatch || signalMatch
              
              if (shouldAddSignalNode) {
                middleNode.children.push(signalNode)
                shouldAddMiddleNode = true
              }
            }
          }

          if (shouldAddMiddleNode) {
            middleNode.expandChildren = keyValid
            topNode.children.push(middleNode)
            shouldAddTopNode = true
          }
        }
      }

      if (shouldAddTopNode) {
        topNode.expandChildren = keyValid
        topNodes.push(topNode)
      }
    }

    treeData.value = topNodes
  }

  watch(searchKey, (newVal) => {
    const key = newVal ?? ''
    updateTreeData(key)
  })

  // 动作
  function initialize(selectedSignalIDs = [], count = 0) {
    originSelectedIds.length = 0
    if (selectedSignalIDs) {
      selectedSignalIDs.forEach(id => {
        originSelectedIds.push(id)
      })
    }
    newSelectedIds.length = 0
    availableCount.value = count
    searchKey.value = ''
    updateTreeData('')
  }

  function addSignal(signalNode) {
    if (signalNode.type && signalNode.type < appoxEnums.SignalTreeNodeType.GeneralSignal) return
    newSelectedIds.push(signalNode.id)
    availableCount.value--
    signalNode.exist = true
  }

  function show(selectedSignalIDs = [], count = 0) {
    return dialogQueue.show({
      onLoaded: () => initialize(selectedSignalIDs, count)
    })
  }

  function hide() {
    dialogQueue.hide(newSelectedIds)
  }

  return {
    // 状态
    isVisible: dialogQueue.isVisible,
    searchKey,
    treeData,
    availableCount,
    // 动作
    initialize,
    addSignal,
    show,
    hide,
    getQueueLength: dialogQueue.getQueueLength.bind(dialogQueue),
    clearQueue: dialogQueue.clearQueue.bind(dialogQueue)
  }
})
